package cn.yueranzs.utils;

import cn.hutool.core.date.DateUtil;
import cn.hutool.json.JSONObject;
import cn.hutool.jwt.JWTUtil;
import cn.hutool.jwt.signers.JWTSigner;
import cn.hutool.jwt.signers.JWTSignerUtil;
import cn.yueranzs.config.JwtConfig;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.stereotype.Component;

import java.nio.charset.StandardCharsets;
import java.util.Map;
import java.util.Set;

/**
 * jwt工具类
 * @author yueranzs
 * @date 2021/11/25 15:55
 */
@Component
public class JwtUtil {


    private static JwtConfig jwtConfig;

    @Autowired
    private void setJwtConfig(JwtConfig jwtConfig){
        JwtUtil.jwtConfig = jwtConfig;
    }

    /**
     * 生成jwt
     * @param payload 数据主体
     * @return
     */
    public String create(Map<String,Object> payload){
        //每个jwt都默认生成一个到期时间
        payload.put("expire_time", DateUtil.current() + jwtConfig.getTokenValidityInSeconds() * 1000);
        //生成私钥
        JWTSigner jwtSigner = JWTSignerUtil.hs256(jwtConfig.getBase64Secret().getBytes(StandardCharsets.UTF_8));
        //生成token
        return JWTUtil.createToken(payload,jwtSigner);
    }

    /**
     * 解析jwt
     * @param token
     * @return
     */
    public JSONObject parse(String token){
        return JWTUtil.parseToken(token).getPayload().getClaimsJson();
    }

    /**
     * 校验token是否正确
     * @param token
     * @return
     */
    public boolean verifyToken(String token){
        //先判断是否到期，再判断是否正确
        if (expiredToken(token)) {
            return JWTUtil.verify(token, jwtConfig.getBase64Secret().getBytes(StandardCharsets.UTF_8));
        }
        return false;
    }

    /**
     * 校验token是否过期
     * @param token
     * @return
     */
    public boolean expiredToken(String token){
        return DateUtil.current() < getExpiredToken(token);
    }

    /**
     * 获取token过期时间
     * @param token
     * @return
     */
    public long getExpiredToken(String token){
        return Long.parseLong(parse(token).get("expire_time").toString());
    }

    /**
     * 获取登录人账号
     * @param token
     * @return
     */
    public String getUserNameToken(String token){
        return parse(token).get("username").toString();
    }

    /**
     * 获取登录人角色集合
     * @param token
     * @return
     */
    public Set<GrantedAuthority> getRolesToken(String token){
        return (Set<GrantedAuthority>) parse(token).get("authorities");
    }

}
